import React, {
 PureComponent, useEffect, useRef, useState,
} from 'react'
import { VariableSizeGrid as Grid } from 'react-window'
import ResizeObserver from 'rc-resize-observer'
import classNames from 'classnames'
import { Table } from 'antd'
import styles from './index.less'

function VirtualTable(props) {
  const { columns, scroll } = props
  const [tableWidth, setTableWidth] = useState(0)

  const widthColumnCount = columns?.filter(({ width }) => !width).length
  const mergedColumns = columns?.map(column => {
    if (column.width) {
      return column
    }

    return {
      ...column,
      width: Math.floor(tableWidth / widthColumnCount),
    }
  })

  const gridRef = useRef()
  const [connectObject] = useState(() => {
    const obj = {}
    Object.defineProperty(obj, 'scrollLeft', {
      get: () => null,
      set: (scrollLeft) => {
        if (gridRef.current) {
          gridRef.current.scrollTo({ scrollLeft })
        }
      },
    })

    return obj
  })

  const resetVirtualGrid = () => {
    gridRef.current?.resetAfterIndices({
      columnIndex: 0,
      shouldForceUpdate: true,
    })
  }

  useEffect(() => resetVirtualGrid, [tableWidth])

  const renderVirtualList = (rawData, { scrollbarSize, ref, onScroll }) => {
    ref.current = connectObject

    return (
      <Grid
        ref={gridRef}
        className="virtual-grid"
        columnCount={mergedColumns.length}
        columnWidth={(index) => {
          const { width } = mergedColumns[index]
          return width
        }}
        height={scroll?.y}
        rowCount={rawData.length}
        rowHeight={() => 54}
        width={tableWidth}
        onScroll={({ scrollLeft }) => {
          onScroll({ scrollLeft })
        }}
      >
        {({
          columnIndex,
          rowIndex,
          style,
        }) => (
          <div
            className={`${classNames('virtual-table-cell', {
              'virtual-table-cell-last': columnIndex === mergedColumns.length - 1,
            })} ${styles.text_overflow_single}`}
            style={{
              padding: '0 20px',
              lineHeight: '50px',
              borderBottom: '1px solid rgba(0, 0, 0, 0.1)',
              ...style,
            }}
            title={(rawData[rowIndex])[(mergedColumns)[columnIndex].dataIndex]}
          >
            {(rawData[rowIndex])[(mergedColumns)[columnIndex].dataIndex]}
          </div>
        )}
      </Grid>
    )
  }

  return (
    <ResizeObserver
      onResize={({ width }) => {
        if (width) {
          setTableWidth(width)
        }
      }}
    >
      <Table
        {...props}
        className="virtual-table"
        columns={mergedColumns}
        pagination={false}
        components={{
          body: renderVirtualList,
        }}
      />
    </ResizeObserver>
  )
}

export default class ResultTable extends PureComponent {
  render() {
    const { columns, dataSource, ...props } = this.props
    return (
      <VirtualTable columns={columns} dataSource={dataSource} scroll={{ y: 300, x: '100vw' }} {...props} />
    )
  }
}
